元组用于将一组相关值存储到单个值中，而不管这些值是什么类型，或有多少个相关值。某些情况下，可能需要解包这样的元组，例如：将其元素作为单独的参数传递给函数。举个简单的例子，可以取一个元组，并将其元素传递给变量print()操作，如第12.4节所述:

\begin{lstlisting}[style=styleCXX]
Tuple<std::string, char const*, int, char> t("Pi", "is roughly",
3, ’\n’);
print(t...); // ERROR: cannot expand a tuple; it isn’t a parameter pack
\end{lstlisting}

如示例中所述，因为不是参数包，所以解包元组的尝试不会成功。可以使用索引列表实现相同的方法。下面的函数模板apply()接受一个函数和一个元组，然后用未打包的元组元素调用该函数:

\hspace*{\fill} \\ %插入空行
\noindent
\textit{tuples/apply.hpp}
\begin{lstlisting}[style=styleCXX]
template<typename F, typename... Elements, unsigned... Indices>
auto applyImpl(F f, Tuple<Elements...> const& t,
					Valuelist<unsigned, Indices...>)
	->decltype(f(get<Indices>(t)...))
{
	return f(get<Indices>(t)...);
}

template<typename F, typename... Elements,
		unsigned N = sizeof...(Elements)>
auto apply(F f, Tuple<Elements...> const& t)
	->decltype(applyImpl(f, t, MakeIndexList<N>()))
{
	return applyImpl(f, t, MakeIndexList<N>());
}
\end{lstlisting}

applyImpl()函数模板接受给定的索引列表，并将元组中的元素展开为其函数对象参数f的参数列表。面向用户的apply()只负责构造初始索引列表，其允许将一个元组扩展为print()的参数:

\begin{lstlisting}[style=styleCXX]
Tuple<std::string, char const*, int, char> t("Pi", "is roughly",
												3, ’\n’);
apply(print, t); // OK: prints Pi is roughly 3
\end{lstlisting}

C++17提供了一个类似的函数，可用于类元组类型。






































